package sis.clocktest;/*
 * @auther 顶风少年
 * @mail dfsn19970313@foxmail.com
 * @date 2019-08-01 16:44
 * @notify
 * @version 1.0
 */

import junit.framework.TestCase;
import sis.clock.Clock;
import sis.clock.ClockListener;
import sis.search.Search;

import java.util.*;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

public class ClockTest extends TestCase {
    //时钟
    private Clock clock;

    private Lock lock;
    private Condition receivedEnoughTics;

    protected void setUp() {
        lock = new ReentrantLock();
        receivedEnoughTics = lock.newCondition();
    }

    // 这个应该是给 锁用的对象
    private Object monitor = new Object();


    public void testClock() throws Exception {
        final int seconds = 2;
        //保存执行时间
        final List<Date> tics = new ArrayList<>();
        ClockListener listener = createClockListener(tics, seconds);
        //启动线程
        clock = new Clock(listener);
        //获取锁
        lock.lock();
        try {
            //主线程等待
            receivedEnoughTics.await();
        } finally {
            //释放锁
            lock.unlock();
        }
        clock.stop();
        verify(tics, seconds);
    }


    private  ClockListener createClockListener(final List<Date> tics, final int seconds) {
        return new ClockListener() {
            private int count = 0;
            @Override
            public void update(Date date) {
                tics.add(date);
                if (++count == seconds) {
                    //获取锁
                    lock.lock();
                    try {
                        //唤醒主线程
                        receivedEnoughTics.signalAll();
                    } finally {
                        //释放锁
                        lock.unlock();
                    }
                }
            }
        };
    }

    private void verify(List<Date> tics, int seconds) {
        //断言执行次数是 5
        assertEquals(seconds, tics.size());
        //断言执行时间间隔1秒
        for (int i = 1; i < seconds; i++) {
            assertEquals(1, getSecondsFromLast(tics, i));
        }
    }




    private long getSecondsFromLast(List<Date> tics, int i) {
        //设置时间
        Calendar calendar = new GregorianCalendar();
        calendar.setTime(tics.get(i));
        //获取秒
        int now = calendar.get(Calendar.SECOND);
        //上一次时间
        calendar.setTime(tics.get(i - 1));
        //上一次的秒
        int then = calendar.get(Calendar.SECOND);
        if (now == 0) {
            now = 60;
        }
        return now - then;
    }


}
